<template>
  <div class="outter">
    <!-- 开头的添加搜索功能区 -->
    <div class="buttonsearch">
      <a-button type="primary" @click="addLineVisible = true"
        ><a-icon type="plus-circle" />新增菜品种类</a-button
      >

      <div class="searchout">
        <a-button type="dashed" @click="reset">重置</a-button>
        <a-input-search
          style="width: 88%"
          placeholder="搜索菜品种类或菜品"
          enter-button
          @search="onSearch"
        ></a-input-search>
      </div>
    </div>
    <a-table
      :columns="columns"
      :pagination="false"
      :scroll="{ y: 400 }"
      :data-source="data"
      bordered
      :fixed="true"
      :loading="tableLoading"
      :defaultExpandAllRows="true"
     
    >
      <!-- 修改名称部分 -->
      <template v-for="col in ['name']" :slot="col" slot-scope="text, record">
        <div :key="col">
          <a-input
            v-if="record.editable"
            style="margin: -5px 0"
            :value="text"
            @change="(e) => handleTchange(e.target.value, record, col)"
          />
          <template v-else>
            {{ text }}
          </template>
        </div>
      </template>
      <!-- 操作方法部分 -->
      <template slot="method" slot-scope="text, record">
        <div class="editable-row-operations">
          <span v-if="record.editable">
            <a-button type="primary" @click="() => tsave(record)"
              >保存</a-button
            >
            <a-divider type="vertical" />
            <a-button @click="() => tcancel(record)">取消</a-button>
          </span>
          <span v-else>
            <a-button :disabled="editingKey !== ''" type="primary" @click="addfood(record)">
                新增菜品
              </a-button>
            <a-divider type="vertical" />
            <a-button
              :disabled="editingKey !== ''"
              @click="() => tedit(record)"
              
              >修改</a-button
            >
            <a-divider type="vertical" />
            <a-popconfirm
              :disabled="editingKey !== ''"
              title="确定删除吗？"
              @confirm="() => deletet(record)"
            >
              <a-button :disabled="editingKey !== ''" type="danger">
                删除
              </a-button>
            </a-popconfirm>
            
             
          </span>
        </div>
      </template>
      <!-- 上传照片部分 -->
      <template slot="img" slot-scope="text, record">
        <a-upload
          name="file"
          :multiple="true"
          accept="image/*"
          :data="
            (file) => {
              return { photo: file, foodId: record.id };
            }
          "
          action="http://8.130.49.254:8889/test"
          @change="
            (info) => {
              handleChange(info, record);
            }
          "
          :show-upload-list="false"
        >
          <a class="uploadimage" href="javascript:;">
            <div class="zhezhao">修改</div>
            <img
              :src="record.img"
              alt=""
              style="height: 40px; width: 40px; border-radius: 10px"
            />
          </a>
        </a-upload>
      </template>
      <!-- 子代个数部分 -->
      <span slot="child" slot-scope="text, record">{{
        record.child.length
      }}</span>
      <!-- 嵌套的子表部分 -->
      <a-table
        slot="expandedRowRender"
        slot-scope="record"
        :columns="innerColumns"
        :data-source="record.child"
        :pagination="false"
      >
        <!-- 修改的前三个框 -->
        <template
          v-for="col in ['name', 'price', 'describe']"
          :slot="col"
          slot-scope="text, record"
        >
          <div :key="col">
            <a-input
              v-if="record.editable"
              style="margin: -5px 0"
              :value="text"
              @change="(e) => handleTchange(e.target.value, record, col)"
            />
            <template v-else>
              {{ text }}
            </template>
          </div>
        </template>
        <template slot="method" slot-scope="text, record">
          <div class="editable-row-operations">
            <span v-if="record.editable">
              <a-button @click="() => tsave(record)" type="primary"
                >保存</a-button
              >
              <a-divider type="vertical" />
              <a-button @click="() => tcancel(record)">取消</a-button>
            </span>
            <span v-else>
              <a-button
                :disabled="editingKey !== ''"
                @click="() => tedit(record)"
                type="primary"
                >修改</a-button
              >
              <a-divider type="vertical" />
              <a-popconfirm
                title="确定删除吗？"
                @confirm="() => deletet(record)"
                :disabled="editingKey !== ''"
              >
                <a-button :disabled="editingKey !== ''" type="danger">
                  删除
                </a-button>
              </a-popconfirm>
            </span>
          </div>
        </template>
        <template slot="img" slot-scope="text, record">
          <a-upload
            name="file"
            :multiple="true"
            accept="image/*"
            :data="
              (file) => {
                return { photo: file, foodId: record.id };
              }
            "
            action="http://8.130.49.254:8889/test"
            @change=" (info) => {
              handleChange(info, record);
            }"
            :show-upload-list="false"
          >
            <a class="uploadimage" href="javascript:;">
              <div class="zhezhao">修改</div>
              <img
                :src="record.img"
                alt=""
                style="height: 40px; width: 40px; border-radius: 10px"
              />
            </a>
          </a-upload>
        </template>
      </a-table>
    </a-table>
    <!-- 添加桌台弹出框 -->
    <a-modal
      title="添加食品类别"
      :visible="addLineVisible"
      :confirm-loading="confirmLoading"
      @ok="submitForm('lineRuleForm')"
      @cancel="handleCancel"
      okText="确认"
      cancelText="取消"
    >
      <a-form-model
        ref="lineRuleForm"
        :model="lineRuleForm"
        :rules="linerule"
        v-bind="layout"
      >
        <a-form-model-item has-feedback label="类别名称" prop="value">
          <a-input v-model="lineRuleForm.value" autocomplete="off" />
        </a-form-model-item>
        <a-form-model-item has-feedback label="图标" prop="img">
          <a-upload
            name="avatar"
            list-type="picture-card"
            class="avatar-uploader"
            :show-upload-list="false"
            accept="image/*"
            :data="
              (file) => {
                return { photo: file, name: lineRuleForm.value };
              }
            "
            action="http://8.130.49.254:8889/test"
            @change="handleaddChange"
          >
            <img
              v-if="imageUrl"
              :src="imageUrl"
              alt="avatar"
              style="width: 128px; height: 128px"
            />
            <div v-else>
              <a-icon :type="addloading ? 'loading' : 'plus'" />
              <div class="ant-upload-text">上传</div>
            </div>
          </a-upload>
        </a-form-model-item>
      </a-form-model>
    </a-modal>
    <a-modal
      title="添加餐品"
      :visible="addFoodVisible"
      :confirm-loading="confirmLoading"
      @ok="submitForm('foodRuleForm')"
      @cancel="handleCancel"
      okText="确认"
      cancelText="取消"
    >
      <a-form-model
        ref="foodRuleForm"
        :model="foodRuleForm"
        :rules="foodrule"
        v-bind="layout"
      >
        <a-form-model-item  label="所属类别" prop="line">
          {{record.name}}
        </a-form-model-item>
        <a-form-model-item has-feedback label="餐品名称" prop="value">
          <a-input v-model="foodRuleForm.value" autocomplete="off" />
        </a-form-model-item>
        <a-form-model-item has-feedback label="餐品价格" prop="price">
          <a-input v-model="foodRuleForm.price" autocomplete="off" />
        </a-form-model-item>
        <a-form-model-item has-feedback label="餐品描述" prop="describe">
          <a-input v-model="foodRuleForm.describe" autocomplete="off" />
        </a-form-model-item>
        <a-form-model-item has-feedback label="图片" prop="img">
          <a-upload
            name="avatar"
            list-type="picture-card"
            class="avatar-uploader"
            :show-upload-list="false"
            accept="image/*"
            :data="
              (file) => {
                return { photo: file, name: foodRuleForm.value };
              }
            "
            action="http://8.130.49.254:8889/test"
            @change="handleaddChange"
          >
            <img
              v-if="imageUrl"
              :src="imageUrl"
              alt="avatar"
              style="width: 128px; height: 128px"
            />
            <div v-else>
              <a-icon :type="addloading ? 'loading' : 'plus'" />
              <div class="ant-upload-text">上传</div>
            </div>
          </a-upload>
        </a-form-model-item>
      </a-form-model>
    </a-modal>
  </div>
</template>

<script>
// 定义四列属性
const columns = [
  {
    title: "菜品种类",
    dataIndex: "name",
    width: "30%",
    align: "center",
    scopedSlots: { customRender: "name" },
  },
  {
    title: "菜品个数",
    dataIndex: "child",
    width: "10%",
    align: "center",
    sorter: (a, b) => a.child - b.child,
    sortDirections: ["descend", "ascend"],
    scopedSlots: { customRender: "child" },
  },
  {
    title: "种类图标",
    dataIndex: "img",
    width: "20%",
    align: "center",
    ellipsis: true,
    scopedSlots: { customRender: "img" },
  },
  {
    title: "操作",
    dataIndex: "method",
    align: "center",
    scopedSlots: { customRender: "method" },
  },
];
const innerColumns = [
  {
    title: "菜品名称",
    dataIndex: "name",
    width: "20%",
    align: "center",
    scopedSlots: { customRender: "name" },
  },
  {
    title: "价格",
    dataIndex: "price",
    align: "center",
    width: "15%",
    sorter: (a, b) => a.price - b.price,
    sortDirections: ["descend", "ascend"],
    scopedSlots: { customRender: "price" },
  },
  {
    title: "描述",
    dataIndex: "describe",
    width: "20%",
    align: "center",
    ellipsis: true,
    scopedSlots: { customRender: "describe" },
  },
  {
    title: "图片",
    dataIndex: "img",
    width: "20%",
    scopedSlots: { customRender: "img" },
    align: "center",
    ellipsis: true,
  },
  {
    title: "操作",
    dataIndex: "method",
    align: "center",
    scopedSlots: { customRender: "method" },
  },
];
// 初始化插入数据
const innerData = [];
for (let i = 0; i < 4; i++) {
  let size;
  innerData.push({
    key: i,
    id: i,
    name: `汉堡`,
    price: "3",
    describe: "超级美味，超级好吃哈哈哈哈",
    img: "https://mis-western-restaurant.oss-cn-guangzhou.aliyuncs.com/images/2022/03/17/57ae9abe-6d6e-4b0c-8693-a53d7cb47241.jpg",
    method: {},
  });
}
const data = [];
for (let i = 0; i < 3; i++) {
  let size;
  data.push({
    key: i,
    id: i,
    name: `汉堡`,
    child: innerData,
    img: "https://mis-western-restaurant.oss-cn-guangzhou.aliyuncs.com/images/2022/03/17/57ae9abe-6d6e-4b0c-8693-a53d7cb47241.jpg",
    method: {},
  });
}

export default {
  data() {
    // 添加菜单类别判断
    let validateLineValue = (rule, value, callback) => {
      if (value === "") {
        callback(new Error("请输入名称"));
      } else if (value.length > 13) {
        callback(new Error("名称不应该过长"));
      } else if (
        this.data.some((item) => {
          return item.name == value;
        })
      ) {
        callback(new Error("已有该类别名称"));
      } else {
        callback();
      }
    };
    let validateFoodValue = (rule, value, callback) => {
      if (value === "") {
        callback(new Error("请输入名称"));
      } else if (value.length > 13) {
        callback(new Error("名称不应该过长"));
      } else if (
        this.data.some((item) => {
            return  item.child.some((i) => {
                if (i.name === value) {
                  return true
                }
              })
        }
        )
      ) {
        callback(new Error("已有该菜品名称"));
      } else {
        callback();
      }
    }
    let validateFoodPrice = (rule, value, callback) => {
      if (!/^\d+$/.test(value)) {
        callback(new Error("价格必须为正纯数字"));
      } else {
        callback();
      }
    }
    //上传弹出框图片判断-共享
    let validateImg = (rule, value, callback) => {
      if (this.imageUrl === "") {
        callback(new Error("请上传图片"));
      } else {
        callback();
      }
    };
    return {
      //菜类form
      lineRuleForm: {
        value: "",
      },
      foodRuleForm:{
        value:"",
        price:"",
        describe:""
      },
      //菜类form规则
      linerule: {
        value: [
          { required: true, validator: validateLineValue, trigger: "change" },
        ],
        img: [{ required: true, validator: validateImg, trigger: "blur" }],
      },
      foodrule:{
        value: [
          { required: true, validator: validateFoodValue, trigger: "change" },
        ],
        price:[
           { required: true, validator: validateFoodPrice, trigger: "change" },
        ],
        img: [{ required: true, validator: validateImg, trigger: "blur" }],
      },
      //弹出框布局
      layout: {
        labelCol: { span: 4 },
        wrapperCol: { span: 14 },
      },
      //上传弹出框图片loading-共享
      addloading: false,
      //添加菜类框是否可见
      addLineVisible: false,
      //添加食物类框是否可见
      addFoodVisible: false,
      //表格Loading
      tableLoading: false,

      //确认提交表单loading-共享
      confirmLoading: false,

      //表格所需
      data,
      //当前添加菜品是哪个菜类
      record:{},
      columns,
      innerColumns,
      //现在在修改的key
      editingKey: "",
      //弹出框的图片src-共享
      imageUrl: "",

      cachedata: [],
    };
  },
  mounted() {
    //创建缓存数据，缓存数据用来在修改取消时恢复
    this.refreshCachedata();
  },
  methods: {
    refreshCachedata() {
      this.cachedata = JSON.parse(JSON.stringify(this.data));
    },
    //修改的四个关键方法
    handleTchange(value, record, column) {
      //newData只是一个临时存放点，关键在于刺激v-if进行判断
      const newData = [...this.data];
      record[column] = value;
      this.data = newData;
    },
    tedit(record) {
      //newData只是一个临时存放点，关键在于刺激v-if进行判断
      const newData = [...this.data];
      this.editingKey = record.key;
      record.editable = true;
      this.data = newData;
    },
    tsave(record) {
      const newData = [...this.data];

      let tarr = Object.values(record);
      let message = "";
      for (let i = 0; i < tarr.length; i++) {
        if (tarr[i] === "") {
          message = "不可有修改项为空！";
          break;
        }
        if (i == 0) {
          if (!record.hasOwnProperty("price")) {
            newData.map((item) => {
              if (item.name === record.name && item.key !== record.key) {
                message = "第一项名称不可重复！";
              }
            });
          } else {
            newData.map((item) => {
              item.child.map((i) => {
                if (i.name === record.name && i.key !== record.key) {
                  message = "第一项名称不可重复！";
                }
              });
            });
          }
          if (record.hasOwnProperty("price") && !/^\d+$/.test(record.price)) {
          message = "价格不可为负数且必须为数字！";
        }
        }
      }
      if (message != "") {
        this.$message.warn(message);
        return;
      }

      delete record.editable;
      this.data = newData;
      this.refreshCachedata();
      this.editingKey = "";
    },
    tcancel(record) {
      //不管是[...this.cachedata]还是object.assign整个付过去都会是浅拷贝，我这个效率最低但最省事
      this.editingKey = "";
      delete record.editable;
      this.data = JSON.parse(JSON.stringify(this.cachedata));
    },
    //查找时
    
    //处理
    handleChange(info, record) {
      console.log(info);
      if (info.file.status !== "uploading") {
        console.log(info.file, info.fileList);
      }
      if (info.file.status === "done") {
        console.log(record);
        record.img = info.file.response;
        this.$message.success(`${info.file.name} 上传成功`);
      } else if (info.file.status === "error") {
        this.$message.error(`${info.file.name} 上传失败.`);
      }
    },
    handleaddChange(info, fileList, event) {
      this.addloading = true;
      if (info.file.status === "done") {
        this.imageUrl = info.file.response;
        this.addloading = false;
      } else if (info.file.status === "error") {
        this.$message.error(`${info.file.name} 上传失败.`);
      }
    },

    //提交表单时
    submitForm(formName) {
      let thing
      let data=[]
      if ((formName === "lineRuleForm")) {
        thing = {
          key: this.lineRuleForm.value,
          id: this.lineRuleForm.value,
          name: this.lineRuleForm.value,
          child: [],
          img: this.imageUrl,
        };
        data=this.data
      } else {
        thing = {
          key: this.foodRuleForm.value,
          id: this.foodRuleForm.value,
          name: this.foodRuleForm.value,
          price:this.foodRuleForm.price,
          describe:this.foodRuleForm.describe,
          img: this.imageUrl,
        };
        data=this.record.child
      }
      this.$refs[formName].validate((valid) => {
        if (valid) {
          this.confirmLoading = true;
          setTimeout(() => {
            this.confirmLoading = false;
            data.push(thing);
            this.refreshCachedata()
            this.$message.success("成功添加");
            this.addLineVisible = false;
            this.addFoodVisible=false;
            this.$refs[formName].resetFields();
          }, 500);
          this.imageUrl = "";
        } else {
          console.log("添加失败");
          return false;
        }
      });
    },

    addfood(record){
      this.record=record
      this.addFoodVisible=true
    },

    //两个弹出框的取消都是这个
    handleCancel() {
      this.addLineVisible = false;
      this.addFoodVisible = false;
    },

    onSearch(){},
    //点击重置按钮时
    reset(){},
    //点击删除按钮时
    delete() {},
  },
};
</script>

<style scoped>
.outter {
  padding: 20px 10px;
}
.bottonheader {
  widows: 100%;
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: 10px;
}
.buttons {
  width: 30%;
  display: flex;
  justify-content: space-between;
  align-items: center;
}
.nima {
  width: 100%;
  height: 420px;
  background: rgb(217, 220, 223);
}

.editable-row-operations a {
  margin-right: 8px;
}
.buttonsearch {
  display: flex;
  justify-content: space-between;
  align-items: center;
  flex-direction: row;
  margin-bottom: 25px;
}
.uploadimage {
  font-size: 1px;
  position: relative;
  /* transition: all 1s; */
}
.zhezhao {
  opacity: 0;
  background-color: rgb(95, 74, 74);
  transition: all 0.5s;
  color: aliceblue;
  position: absolute;
  width: 40px;
  text-align: center;
  line-height: 40px;
  border-radius: 10px;
}
.uploadimage:hover .zhezhao {
  opacity: 0.6;
}
.searchout {
  width: 50%;
}

.avatar-uploader > .ant-upload {
  width: 128px;
  height: 128px;
}
.ant-upload-select-picture-card i {
  font-size: 32px;
  color: #999;
}

.ant-upload-select-picture-card .ant-upload-text {
  margin-top: 8px;
  color: #666;
}
</style>
